#pragma once

#include "il2cpp-config.h"

// These types are defined in Mono headers included from debugger-agent.c, so just
// forward delcare them.
struct MonoContext;
struct MonoJitInfo;
struct MonoThreadUnwindState;
struct HandleStackMark;
struct SeqPoint;

// These types are not defined in any Mono headers that get included via debugger-agent.c
// so we can "define" them as incomplete types here.
typedef struct MonoLMF MonoLMF;
typedef struct MonoSeqPointInfo MonoSeqPointInfo;

#if IL2CPP_COMPILER_MSVC
DO_MONO_API(int, mono_gc_register_root, (char* start, size_t size, MonoGCDescriptor descr, int32_t source, void *key, const char* msg))
DO_MONO_API_NOT_EXPORTED(int, mono_gc_register_root_wbarrier, (char *start, size_t size, MonoGCDescriptor descr, int32_t source, void *key, const char *msg))
#else
#if defined(__cplusplus)
enum MonoGCRootSource : int32_t;
#endif
DO_MONO_API(int, mono_gc_register_root, (char* start, size_t size, MonoGCDescriptor descr, MonoGCRootSource source, void *key, const char* msg))
DO_MONO_API_NOT_EXPORTED(int, mono_gc_register_root_wbarrier, (char *start, size_t size, MonoGCDescriptor descr, MonoGCRootSource source, void *key, const char *msg))
#endif

DO_MONO_API(uint32_t, mono_image_get_entry_point, (MonoImage * image))
DO_MONO_API(const char*, mono_image_get_filename, (MonoImage * image))
DO_MONO_API(const char*, mono_image_get_guid, (MonoImage * image))
DO_MONO_API(int32_t, mono_image_is_dynamic, (MonoImage * image))
DO_MONO_API(MonoAssembly*, mono_image_get_assembly, (MonoImage * image))
DO_MONO_API(const char*, mono_image_get_name, (MonoImage * image))
DO_MONO_API(MonoDomain*, mono_get_root_domain, (void))
DO_MONO_API(MonoDomain*, mono_domain_get, (void))
DO_MONO_API(int32_t, mono_domain_set, (MonoDomain * domain, int32_t force))
DO_MONO_API(void, mono_domain_foreach, (MonoDomainFunc func, void* user_data))
DO_MONO_API_NOT_EXPORTED(void, mono_domain_lock, (MonoDomain * domain))
DO_MONO_API_NOT_EXPORTED(void, mono_domain_unlock, (MonoDomain * domain))
DO_MONO_API(const MonoAssembly*, mono_domain_get_corlib, (MonoDomain * domain))
DO_MONO_API(MonoAssembly*, mono_domain_get_assemblies_iter, (MonoAppDomain * domain, void** iter))
DO_MONO_API(MonoClass*, mono_type_get_class, (MonoType * type))
DO_MONO_API_NOT_EXPORTED(MonoGenericClass*, m_type_get_generic_class, (MonoType * type))
DO_MONO_API(int32_t, mono_type_is_struct, (MonoType * type))
DO_MONO_API(int32_t, mono_type_is_reference, (MonoType * type))
DO_MONO_API(int32_t, mono_type_generic_inst_is_valuetype, (MonoType * monoType))
DO_MONO_API(char*, mono_type_full_name, (MonoType * type))
DO_MONO_API(char*, mono_type_get_name_full, (MonoType * type, MonoTypeNameFormat format))
DO_MONO_API_NOT_EXPORTED(MonoReflectionType*, mono_type_get_object_checked, (MonoDomain * domain, MonoType * type, MonoError * error))
DO_MONO_API(int, mono_type_get_type, (MonoType * type));
DO_MONO_API(int32_t, mono_type_is_byref, (MonoType * type));
DO_MONO_API(uint32_t, mono_type_get_attrs, (MonoType * type));
DO_MONO_API(uint32_t, mono_type_get_attrs, (MonoType * type));
DO_MONO_API(MonoVTable*, mono_class_vtable, (MonoDomain * domain, MonoClass * klass))
DO_MONO_API(int32_t, mono_class_instance_size, (MonoClass * klass))
DO_MONO_API(int32_t, mono_class_value_size, (MonoClass * klass, uint32_t * align))
DO_MONO_API(int32_t, mono_class_is_assignable_from, (MonoClass * klass, MonoClass * oklass))
DO_MONO_API(MonoClass*, mono_class_from_mono_type, (MonoType * type))
DO_MONO_API(uint32_t, mono_class_get_flags, (MonoClass * klass))
DO_MONO_API(int, mono_class_num_fields, (MonoClass * klass))
DO_MONO_API(int, mono_class_num_methods, (MonoClass * klass))
DO_MONO_API(int, mono_class_num_properties, (MonoClass * klass))
DO_MONO_API(MonoClassField*, mono_class_get_fields, (MonoClass * klass, void* * iter))
DO_MONO_API(MonoMethod*, mono_class_get_methods, (MonoClass * klass, void* * iter))
DO_MONO_API(MonoProperty*, mono_class_get_properties, (MonoClass * klass, void* * iter))
DO_MONO_API(MonoClass*, mono_class_get_nested_types, (MonoClass * monoClass, void* *iter))
DO_MONO_API_NOT_EXPORTED(void, mono_class_setup_methods, (MonoClass * klass))
DO_MONO_API_NOT_EXPORTED(void, mono_class_setup_vtable, (MonoClass * klass))
DO_MONO_API_NOT_EXPORTED(GPtrArray*, mono_class_get_methods_by_name, (MonoClass * il2cppMonoKlass, const char* name, uint32_t bflags, int32_t ignore_case, int32_t allow_ctors, MonoError * error))
DO_MONO_API(MonoMethod*, mono_class_get_method_from_name, (MonoClass * klass, const char* name, int argsCount))
DO_MONO_API_NOT_EXPORTED(int32_t, mono_class_is_abstract, (MonoClass * klass));
DO_MONO_API_NOT_EXPORTED(int32_t, mono_class_field_is_special_static, (MonoClassField * field))
DO_MONO_API(MonoGenericContext*, mono_class_get_context, (MonoClass * klass))
DO_MONO_API_NOT_EXPORTED(MonoMethod*, mono_class_inflate_generic_method_full_checked, (MonoMethod * method, MonoClass * klass_hint, MonoGenericContext * context, MonoError * error))
DO_MONO_API_NOT_EXPORTED(MonoMethod*, mono_class_inflate_generic_method_checked, (MonoMethod * method, MonoGenericContext * context, MonoError * error))
DO_MONO_API_NOT_EXPORTED(int32_t, mono_class_is_nullable, (MonoClass * klass))
DO_MONO_API_NOT_EXPORTED(MonoGenericContainer*, mono_class_get_generic_container, (MonoClass * klass))
DO_MONO_API_NOT_EXPORTED(void, mono_class_setup_interfaces, (MonoClass * klass, MonoError * error))
DO_MONO_API(int32_t, mono_class_is_valuetype, (MonoClass * klass))
DO_MONO_API_NOT_EXPORTED(MonoClass*, mono_class_from_generic_parameter_internal, (MonoGenericParam * param))
DO_MONO_API_NOT_EXPORTED(MonoGenericClass*, mono_class_get_generic_class, (MonoClass * monoClass))
DO_MONO_API_NOT_EXPORTED(MonoClass*, mono_class_try_load_from_name, (MonoImage * image, const char* namespaze, const char* name))
DO_MONO_API_NOT_EXPORTED(int32_t, mono_class_is_gtd, (MonoClass * klass))
DO_MONO_API_NOT_EXPORTED(int32_t, mono_class_is_ginst, (MonoClass * klass))
DO_MONO_API(const char*, mono_class_get_namespace, (MonoClass * klass))
DO_MONO_API(const char*, mono_class_get_name, (MonoClass * klass))
DO_MONO_API(MonoClass*, mono_class_get_parent, (MonoClass * klass))
DO_MONO_API(MonoType*, mono_class_get_type, (MonoClass * klass))
DO_MONO_API(uint32_t, mono_class_get_type_token, (MonoClass * klass))
DO_MONO_API(MonoType*, mono_class_get_byref_type, (MonoClass * klass))
DO_MONO_API(MonoImage*, mono_class_get_image, (MonoClass * klass))
DO_MONO_API(MonoClass*, mono_class_get_interfaces, (MonoClass * klass, void* *iter))
DO_MONO_API_NOT_EXPORTED(int32_t, mono_class_is_interface, (MonoClass * klass))
DO_MONO_API(int, mono_class_get_rank, (MonoClass * klass))
DO_MONO_API(MonoClass*, mono_class_get_element_class, (MonoClass * klass))
DO_MONO_API(int32_t, mono_class_is_enum, (MonoClass * klass))
DO_MONO_API(MonoMethodSignature*, mono_method_signature, (MonoMethod * m))
DO_MONO_API(void, mono_free_method_signatures, ())
DO_MONO_API(MonoDebugLocalsInfo*, mono_debug_lookup_locals, (MonoMethod * method))
DO_MONO_API(void, mono_debug_free_locals, (MonoDebugLocalsInfo * info))
DO_MONO_API(MonoDebugMethodJitInfo*, mono_debug_find_method, (MonoMethod * method, MonoDomain * domain))
DO_MONO_API(void, mono_method_get_param_names, (MonoMethod * method, const char **names))
DO_MONO_API(MonoGenericContext*, mono_method_get_context, (MonoMethod * method))
DO_MONO_API(MonoMethodHeader*, mono_method_get_header_checked, (MonoMethod * method, MonoError * error))
DO_MONO_API(void, mono_metadata_free_mh, (MonoMethodHeader * mh))
DO_MONO_API(char*, mono_method_full_name, (MonoMethod * method, int32_t signature))
DO_MONO_API(MonoGenericContainer*, mono_method_get_generic_container, (MonoMethod * method))
DO_MONO_API_NOT_EXPORTED(void*, mono_method_get_wrapper_data, (MonoMethod * method, uint32_t id))
DO_MONO_API(MonoMethod*, mono_method_get_declaring_generic_method, (MonoMethod * method))
DO_MONO_API(const char*, mono_method_get_name, (MonoMethod * method))
DO_MONO_API(MonoClass*, mono_method_get_class, (MonoMethod * method))
DO_MONO_API(uint32_t, mono_method_get_flags, (MonoMethod * method, uint32_t * iflags))
DO_MONO_API(uint32_t, mono_method_get_token, (MonoMethod * method))
DO_MONO_API(bool, mono_method_is_generic, (MonoMethod * method))
DO_MONO_API(bool, mono_method_is_inflated, (MonoMethod * method))
DO_MONO_API(int32_t, mono_array_element_size, (MonoClass * ac));
DO_MONO_API_NOT_EXPORTED(char*, mono_array_addr_with_size, (MonoArray * array, int size, uintptr_t idx))
DO_MONO_API(uintptr_t, mono_array_length, (MonoArray * array))
DO_MONO_API(const char*, mono_field_get_name, (MonoClassField * field))
DO_MONO_API(void, mono_field_set_value, (MonoObject * obj, MonoClassField * field, void *value))
DO_MONO_API(void, mono_field_static_set_value, (MonoVTable * vt, MonoClassField * field, void *value))
DO_MONO_API_NOT_EXPORTED(void, mono_field_static_get_value_checked, (MonoVTable * vt, MonoClassField * field, void* value, MonoError * error))
DO_MONO_API_NOT_EXPORTED(void, mono_field_static_get_value_for_thread, (MonoInternalThread * thread, MonoVTable * vt, MonoClassField * field, void* value, MonoError * error))
DO_MONO_API_NOT_EXPORTED(MonoObject*, mono_field_get_value_object_checked, (MonoDomain * domain, MonoClassField * field, MonoObject * obj, MonoError * error))
DO_MONO_API(uint32_t, mono_field_get_offset, (MonoClassField * field))
DO_MONO_API(MonoClass*, mono_field_get_parent, (MonoClassField * field))
DO_MONO_API(MonoType*, mono_field_get_type, (MonoClassField * field))
DO_MONO_API(uint16_t*, mono_string_chars, (MonoString * s))
DO_MONO_API(int, mono_string_length, (MonoString * s))
DO_MONO_API(MonoString*, mono_string_new, (MonoDomain * domain, const char *text))
DO_MONO_API_NOT_EXPORTED(MonoString*, mono_string_new_checked, (MonoDomain * domain, const char *text, MonoError * merror))
DO_MONO_API(char*, mono_string_to_utf8_checked, (MonoString * string_obj, MonoError * error))
DO_MONO_API(int, mono_object_hash, (MonoObject * obj))
DO_MONO_API(void*, mono_object_unbox, (MonoObject * obj))
DO_MONO_API(MonoMethod*, mono_object_get_virtual_method, (MonoObject * obj, MonoMethod * method))
DO_MONO_API_NOT_EXPORTED(MonoObject*, mono_object_new_checked, (MonoDomain * domain, MonoClass * klass, MonoError * error))
DO_MONO_API(MonoType*, mono_object_get_type, (MonoObject * object))
DO_MONO_API(MonoClass*, mono_object_get_class, (MonoObject * obj))
DO_MONO_API_NOT_EXPORTED(MonoMethod*, mono_get_method_checked, (MonoImage * image, uint32_t token, MonoClass * klass, MonoGenericContext * context, MonoError * error))
DO_MONO_API(uint32_t, mono_gchandle_new_weakref, (MonoObject * obj, int32_t track_resurrection))
DO_MONO_API(MonoObject*,  mono_gchandle_get_target, (uint32_t gchandle))
DO_MONO_API(void, mono_gchandle_free, (uint32_t gchandle))
DO_MONO_API(MonoThread*, mono_thread_current, ())
DO_MONO_API(MonoThread*, mono_thread_get_main, ())
DO_MONO_API(MonoThread*, mono_thread_attach, (MonoDomain * domain))
DO_MONO_API(void, mono_thread_detach, (MonoThread * thread))
DO_MONO_API_NOT_EXPORTED(MonoInternalThread*, mono_thread_internal_current, ())
DO_MONO_API_NOT_EXPORTED(int32_t, mono_thread_internal_is_current, (MonoInternalThread * thread))
DO_MONO_API_NOT_EXPORTED(void, mono_thread_internal_abort, (MonoInternalThread * thread, int32_t appdomain_unload))
DO_MONO_API_NOT_EXPORTED(void, mono_thread_internal_reset_abort, (MonoInternalThread * thread))
DO_MONO_API_NOT_EXPORTED(uint16_t*, mono_thread_get_name, (MonoInternalThread * this_obj, uint32_t * name_len))
DO_MONO_API_NOT_EXPORTED(void, mono_thread_set_name_internal, (MonoInternalThread * this_obj, MonoString * name, int32_t permanent, int32_t reset, MonoError * error))
DO_MONO_API(void, mono_thread_suspend_all_other_threads, ())
DO_MONO_API(int32_t, mono_thread_state_init_from_current, (MonoThreadUnwindState * ctx))
DO_MONO_API(int32_t, mono_thread_state_init_from_monoctx, (MonoThreadUnwindState * ctx, MonoContext * mctx))
DO_MONO_API(const char*, mono_property_get_name, (MonoProperty * prop))
DO_MONO_API(MonoMethod*, mono_property_get_get_method, (MonoProperty * prop))
DO_MONO_API(MonoMethod*, mono_property_get_set_method, (MonoProperty * prop))
DO_MONO_API(MonoClass*, mono_property_get_parent, (MonoProperty * prop))
DO_MONO_API_NOT_EXPORTED(void, mono_loader_lock, ())
DO_MONO_API_NOT_EXPORTED(void, mono_loader_unlock, ())
DO_MONO_API_NOT_EXPORTED(void, mono_loader_lock_track_ownership, (int32_t track))
DO_MONO_API_NOT_EXPORTED(int32_t, mono_loader_lock_is_owned_by_self, ())
DO_MONO_API_NOT_EXPORTED(void, mono_gc_wbarrier_generic_store, (void* ptr, MonoObject * value))
DO_MONO_API_NOT_EXPORTED(void, mono_gc_base_init, ())
DO_MONO_API_NOT_EXPORTED(void, mono_gc_deregister_root, (char* addr))
DO_MONO_API_NOT_EXPORTED(void*, mono_gc_make_root_descr_all_refs, (int numbits))
DO_MONO_API_NOT_EXPORTED(MonoGCDescriptor, mono_gc_make_vector_descr, ())
DO_MONO_API(MonoInterpCallbacks*, mini_get_interp_callbacks, ())
DO_MONO_API_NOT_EXPORTED(int32_t, mono_gc_is_moving, ())
DO_MONO_API_NOT_EXPORTED(void*, mono_gc_invoke_with_gc_lock, (MonoGCLockedCallbackFunc func, void *data))
DO_MONO_API_NOT_EXPORTED(int, mono_reflection_parse_type_checked, (char *name, MonoTypeNameParse * info, MonoError * error))
DO_MONO_API_NOT_EXPORTED(void, mono_reflection_free_type_info, (MonoTypeNameParse * info))
DO_MONO_API_NOT_EXPORTED(MonoType*, mono_reflection_get_type_checked, (MonoImage * rootimage, MonoImage * image, MonoTypeNameParse * info, int32_t ignorecase, int32_t * type_resolve, MonoError * error))
DO_MONO_API(void, mono_runtime_quit, ())
DO_MONO_API(int32_t, mono_runtime_is_shutting_down, ())
DO_MONO_API_NOT_EXPORTED(MonoObject*, mono_runtime_try_invoke, (MonoMethod * method, void* obj, void** params, MonoObject** exc, MonoError * error))
DO_MONO_API_NOT_EXPORTED(MonoObject*, mono_runtime_invoke_checked, (MonoMethod * method, void* obj, void** params, MonoError * error))
DO_MONO_API_NOT_EXPORTED(int32_t, mono_runtime_try_shutdown, ())
DO_MONO_API(void, mono_arch_setup_resume_sighandler_ctx, (MonoContext * ctx, void* func))
DO_MONO_API(void, mono_arch_set_breakpoint, (MonoJitInfo * ji, uint8_t * ip))
DO_MONO_API(void, mono_arch_clear_breakpoint, (MonoJitInfo * ji, uint8_t * ip))
DO_MONO_API(void, mono_arch_start_single_stepping, ())
DO_MONO_API(void, mono_arch_stop_single_stepping, ())
DO_MONO_API(void, mono_arch_skip_breakpoint, (MonoContext * ctx, MonoJitInfo * ji))
DO_MONO_API(void, mono_arch_skip_single_step, (MonoContext * ctx))
DO_MONO_API(intptr_t, mono_arch_context_get_int_reg, (MonoContext * ctx, int reg))
DO_MONO_API(void, mono_arch_context_set_int_reg, (MonoContext * ctx, int reg, intptr_t val))
DO_MONO_API(MonoJitInfo*, mono_jit_info_table_find, (MonoDomain * domain, char* addr))
DO_MONO_API(MonoMethod*, mono_jit_info_get_method, (MonoJitInfo * ji))
DO_MONO_API_NOT_EXPORTED(MonoJitInfo*, mono_jit_info_table_find_internal, (MonoDomain * domain, char* addr, int32_t try_aot, int32_t allow_trampolines))
DO_MONO_API(int32_t, mono_debug_il_offset_from_address, (MonoMethod * method, MonoDomain * domain, uint32_t native_offset))
DO_MONO_API(void, mono_set_is_debugger_attached, (int32_t attached))
DO_MONO_API_NOT_EXPORTED(uint32_t, mono_aligned_addr_hash, (const void* ptr))
DO_MONO_API_NOT_EXPORTED(MonoGenericInst*, mono_metadata_get_generic_inst, (int type_argc, MonoType** type_argv))
DO_MONO_API_NOT_EXPORTED(void*, mono_ldtoken_checked, (MonoImage * image, uint32_t token, MonoClass** handle_class, MonoGenericContext * context, MonoError * error))
DO_MONO_API_NOT_EXPORTED(void, mono_stack_mark_record_size, (MonoThreadInfo * info, HandleStackMark * stackmark, const char* func_name))
DO_MONO_API_NOT_EXPORTED(void, mono_nullable_init, (uint8_t * buf, MonoObject * value, MonoClass * klass))
DO_MONO_API_NOT_EXPORTED(MonoObject*, mono_value_box_checked, (MonoDomain * domain, MonoClass * klass, void* value, MonoError * error))
DO_MONO_API(char*, mono_get_runtime_build_info, ())
DO_MONO_API(MonoMethod*, mono_marshal_method_from_wrapper, (MonoMethod * wrapper))
DO_MONO_API(void*, mono_jit_find_compiled_method_with_jit_info, (MonoDomain * domain, MonoMethod * method, MonoJitInfo** ji))
DO_MONO_API(MonoLMF**, mono_get_lmf_addr, ())
DO_MONO_API(void, mono_set_lmf, (MonoLMF * lmf))
DO_MONO_API(void, mono_aot_get_method_checked, (MonoDomain * domain, MonoMethod * method, MonoError * error))
DO_MONO_API(MonoJitInfo*, mini_jit_info_table_find, (MonoDomain * domain, char* addr, MonoDomain** out_domain))
DO_MONO_API(void, mono_restore_context, (MonoContext * ctx))
DO_MONO_API_NOT_EXPORTED(MonoString*, mono_ldstr_checked, (MonoDomain * domain, MonoImage * image, uint32_t idx, MonoError * error))
DO_MONO_API(int32_t, mono_find_prev_seq_point_for_native_offset, (MonoDomain * domain, MonoMethod * method, int32_t native_offset, MonoSeqPointInfo **info, SeqPoint * seq_point))
DO_MONO_API(int32_t, mono_environment_exitcode_get, ())
DO_MONO_API(void, mono_environment_exitcode_set, (int32_t value))
DO_MONO_API_NOT_EXPORTED(void, mono_threadpool_suspend, ())
DO_MONO_API_NOT_EXPORTED(void, mono_threadpool_resume, ())
DO_MONO_API(MonoImage*, mono_assembly_get_image, (MonoAssembly * assembly))
DO_MONO_API_NOT_EXPORTED(int32_t, mono_verifier_is_method_valid_generic_instantiation, (MonoMethod * method))
DO_MONO_API_NOT_EXPORTED(void, mono_network_init, ())
DO_MONO_API(MonoMethod*, jinfo_get_method, (MonoJitInfo * ji))
DO_MONO_API_NOT_EXPORTED(MonoGenericContext*, mono_generic_class_get_context, (MonoGenericClass * gclass))
DO_MONO_API(MonoClass*, mono_get_string_class, ())
